home *** CD-ROM | disk | FTP | other *** search
Text File | 1995-01-04 | 40.7 KB | 2,198 lines |
-
-
-
- LENGUAJE C
-
- CONTROL DE DISQUETERAS
-
- Para mejorar la presentación de un programa es importante tener un
- control total de todos los errores que se puedan presentar. Una buena
- fuente de problemas son los accesos a las disqueteras. Por ejemplo,
- un problema muy clásico es el intento de acceso a una disquetera sin
- disco, pues nos encontramos ante el clásico mensaje de «Anular,
- Repetir, Descartar?», algo poco deseable dentro de un programa.
- Avisar de todos los problemas que se puedan presentar es una buena
- forma de mejorar la calidad de un programa.
-
- Mediante la rutina biosdisk podemos saber el estado de la disquetera y
- así evitar los errores que acabamos de mencionar. Por ejmplo, antes
- de abrir un fichero de un disco, podemos ver si realmente está el
- disco en la disquetera, y en caso afirmativo, abrirlo. Para comprobar
- el estado podemos utilizar el siguiente código:
-
- #include <bios.h>
-
- main() {
-
- int r, unidad = 0;
-
- char b[512];
-
- r=biosdisk(4,unidad,0,0,0,1,b);
-
- r=biosdisk(4,unidad,0,0,0,1,b);
-
- switch(r) {
-
- case 0x02: printf("Disco no formateado");break;
-
- case 0x08:
-
- case 0x09: printf("Fallo en el DMA");break;
-
- case 0x0C: printf("Tipo de disco no encontrado");break;
-
- case 0x10: printf("Error en el CRC");break;
-
- case 0x20: printf("Fallo en la controladora");break;
-
- case 0x40: printf("Fallo de búsqueda");break;
-
- case 0x80: printf("No hay disco en la disquetera");break;
-
- default : printf("Ok");break;
-
- }
-
- }
-
-
- La variable unidad vale 0 para A: y 1 para B:. Se llama dos veces
- seguidas a la función biosdisk, ya que la primera vez devuelve un valor
- que indica si se ha encontrado un disco, pero sin ver su estado.
-
- Ricard Forner Gili
-
- Barcelona
-
-
- SUPER PIXEL
-
- Este programa (realizado en «Quick C» de Microsoft, aunque fácilmente
- implementable en «Turbo C») nos proporciona una nueva rutina para
- imprimir un pixel en una VGA 640x480. La nueva rutina está realizada
- en ensamblador y proporciona una mayor velocidad que la instrucción
- «_setpixel». En este programa podemos comparar las dos instrucciones
- para ver la diferencia de velocidad de una a otra.
-
- #include <graph.h>
-
- void DP(int pagina,int i,int p,int color);
-
- main()
-
- {
- int x,y;char ca;
-
- _setvideomode(_VRES16COLOR);
-
- _clearscreen(_GCLEARSCREEN);
-
- printf("1.- Impresión en 'C' (setpixel).\n");
-
- printf("2.- Impresión 'ASSEMBLY' (dp).\n");
-
- while (ca!='1' && ca!='2') ca=getch();
-
- for (y=0;y<480;y=y+10)
-
- for (x=0;x<640;x=x+1)
-
- if (ca=='1') {_setcolor(1);_setpixel(x,y);}
-
- else DP(0,x,y,1);
-
- _setvideomode(_DEFAULTMODE);
-
- }
-
- void DP(int pagina,int t,int p,int color)
-
- {
-
- _asm{
-
- mov bh,[bp+6];
-
- mov cx,[bp+8];
-
- mov dx,[bp+10];
-
- mov al,[bp+12];
-
- mov ah,0Ch;
-
- int 10h;
-
- }
-
- }
-
- Juan Vercher Martínez
-
- Gandía (Valencia)
-
-
-
- INCLUYA 16 COLORES EN EL FONDO
-
- Este programa es un ejempo de cómo utilizar los colores comprendidos
- entre el 8 y el 15 como color de fondo. Hemos de recordar que para el
- color de fondo sólo podemos utilizar los colores del 0 al 7, de ahí la
- motivación de este truco.
-
- La rutina «parpadeo()» funciona por medio de la interrupción 10h
- subservicio 03h, que permite activar o desactivar el atributo de
- parpadeo. La ROM BIOS utiliza el parpadeo por defecto, pero cambiando
- el valor del atributo se pueden utilizar los 16 colores para el fondo.
- El valor que se pasa en BL determina si el valor está activado (01h) o
- desactivado (00h).
-
- Es necesario utilizar la función «textattr()» (para definir los dos
- colores se puede emplear la fórmula ColorTexto+ColorFondo*16) para
- cambiar el color, ya que con las funciones «textcolor()» y
- «textbackground()» no es posible, puesto que reestablecen el atributo
- para parpadeo.
-
- #include <stdio.h>
-
- #include <dos.h>
-
- #include <conio.h>
-
- enum BOOLEAN {OFF, ON};
-
- void parpadeo (enum BOOLEAN activar);
-
- void parpadeo (enum BOOLEAN activar)
-
- {
-
- union REGS regs;
-
- regs.h.bl=activar ? 0x01 : 0x00;
-
- regs.h.ah=0x10;
-
- regs.h.al=0x03;
-
- int86(0x10,®s,®s);
-
- }
-
- void main()
-
- {
-
- int i,j;
-
- enum BOOLEAN parpadear;
-
- textattr( 0 + 15 * 16);
-
- cprintf("\n\rFONDO");
-
- for(i=1;i<16;i++) cprintf(" %2d ",i);
-
- for(i=0;i<16;i++)
-
- for (j=0;j<16;j++)
-
- {
-
- textattr(i+j*16);
-
- cprintf("Texto");
-
- }
-
- textattr(0+15*16);
-
- cprintf("Pulsa Esc para finalizar, otra tecla "
-
- "para cambiar el atributo de parpadeo...");
-
- parpadear = ON;
-
- while(i!=27)
-
- {
-
- parpadear=!parpadear;
-
- parpadeo(parpadear);
-
- i=getch();
-
- }
-
- parpadeo(ON);
-
- }
-
-
- Antonio Jesús Ollero Sanguino
-
- Casar de Cáceres (Cáceres)
-
-
-
- TECLADOS VELOCES
-
- La ROM-BIOS permite obtener las teclas pulsadas a una velocidad máxima
- de 30 caracteres por segundo y con un retardo de autorrepetición de
- 0,25 segundos. Algunas veces interesa que el retardo de
- autorrepetición sea menor y leer a más velocidad. Esta rutina
- soluciona este problema.
-
- #include <Dos.h>
-
- usigned char obt_tecla (void);
-
- {
-
- unsigned int *cabeza=(unsigned int *) (0x0000041a);
-
- unsigned int *cola=(unsigned int *) (0x0000041c);
-
- *cabeza=*cola
-
- return portb(0x60);
-
- }
-
- El funcionamiento de la rutina está basado en la lectura del código de
- letra pulsada directamente del puerto, y además se vacía el buffer del
- teclado para que no se llene, ya que no se saca la tecla mediante
- ninguna llamada a la ROM-BIOS.
-
- Utilidad: Esta función puede ser de gran utilidad para juegos, en los
- cuales se requiere mover un gráfico o ejecutar una acción según la
- tecla pulsada. En estos casos suele resultar bastante lento tener que
- esperar los 0,25 segundos para que el ordenador detecte que se
- mantiene pulsada la misma tecla.
-
- Jorge Pastor Mondejar
-
- Molina de Segura (Murcia)
-
-
- SCROLL DE TEXTO
-
- Esta rutina realiza un scroll en pantalla mediante el uso de las
- interrupciones de la BIOS. La ventaja de esta técnica radica en que
- permite la realización un scroll en una ventana.
-
- Los parámetros que se le pasan a la rutina son los siguientes:
-
- Fijo: atributo; este parámetro representa el color.
-
- Fil: fila superior de la ventana donde se realiza el
- scroll.
-
- Col: columna más a la izquierda de la ventana donde se hace el
- scroll.
-
- Fils: fila inferior de la ventana donde se realiza el
- scroll.
-
- Col: columna más a la derecha de la ventana donde se hace el
- scroll.
-
- Atr: Función a realizar. Dependiendo de los parámetros que le
- pasemos aquí podrá realizar «scroles» hacia arriba, abajo, etc, (es
- conveniente investigar).
-
- Numfils: número de líneas a mover.
-
- #include <bios.h>
-
- #include <stdio.h>
-
- #include <conio.h>
-
- union REGS inregs, outregs;
-
- void scroll (int fijo, int fil, int col, int fils, int cols, int atr,
- int numfils)
-
- {
-
- inregs.h.ah = atr;
-
- inregs.h.al = numfils;
-
- inregs.h.bh = fijo;
-
- inregs.h.ch = fil;
-
- inregs.h.cl = col;
-
- inregs.h.dh = fils;
-
- inregs.h.dl = cols;
-
- int86(0x10, &inregs, &outregs);
-
- }
-
- /* Programa de ejemplo */
-
- main()
-
- {
-
- int i,u;
-
- clrscr();
-
- for (i=0; i<30; i++)
-
- {
-
- gotoxy(50,3);
-
- printf("%d",i);
-
- scroll(7,2,49,19,60,7,1);
-
- getch();
-
- }
-
- }
-
- David G. Peris
-
- Barcelona
-
-
- SALIR AL DOS
-
- El objetivo de esta rutina es el de poder implementar un shell al DOS
- en los menús de nuestros propios programas.
-
- Para realizar este cometido invocaremos una llamada al «command.com»
- mediante la orden «SYSTEM», una vez que sepamos que el interprete de
- comandos está en nuestro path activo. Si el «command.com» no se
- encuentra en el path activo, sale de la función devolviendo 0, si no
- lo ejecuta y cuando se teclea «EXIT» devuelve 1.
-
- Para saber si el «command.com» está a nuestra disposición, utilizamos
- la sentencia «SEARCHPATH» de la líbreria <dir.h>. Si el «command.com»
- está disponible devuelve la ruta completa de acceso a él; en caso
- contrario devuelve «NULL».
-
- El programa ha sido compilado mediante «Turbo C/C++ 1.0».
-
- #include <dir.h>
-
- #include <stdlib.h>
-
- #include <conio.h>
-
- int dos_shell();
-
- /* main de ejemplo */
-
- main ()
-
- {
-
- if dos_shell()==0)
-
- cprintf("\nNo se encontró COMMAND COM en el path activo\n");
-
- return 0;
-
- }
-
- int dos_shell()
-
- {
-
- char *camino=NULL;
-
- camino =searchpath("COMMAND.COM");
-
- if (camino==NULL) return 0;
-
- clrscr();
-
- cprintf ("Teclea Exit para volver al programa. \n");
-
- system (camino);
-
- clrscr();
-
- return 1;
-
- }
-
- José Luis Moncada Collado
-
- Sant Adriá de Besós (Barcelona)
-
-
-
- EFECTO OPTICO
-
- Este es un pequeño truco para lograr esos efectos «visuales» que tanto
- suelen gustar a la gente. Consiste en un CLS muy llamativo, ya que
- todo lo que hay en la pantalla de texto desaparecerá como si de niebla
- o humo se tratase. Es ideal para programas en modo texto que no
- pueden acceder a los trucos que permite el modo gráfico.
-
- El programa accede directamente al buffer de vídeo y ahí va
- incrementando en uno todos los caracteres distintos de 0 (para evitar
- un bucle infinito) y todos los distintos de « » (para no tocar el
- fondo, sólo el texto), así hasta que no quedan más que ceros o « »
- (espacio en blanco) entonces ya se habrá borrado la pantalla.
- Funciona tanto en color como en monocromo, y está realizado con el
- Borland C++ 3.1 en ANSI C. Por lo que debería funcionar sin problemas
- en cualquier compilador de C que cumpla la norma ANSI.
-
- #include <stdio.h>;
-
- #include <dos.h>;
-
- #include <stdlib.h>;
-
- int modo_video(void),modov,humo(void);
-
- char far *mem_video;
-
- main()
-
- {
-
- modov=modo_video();
-
- if ((modov!=2) && (modov!=3) && (modov!=7)) {
-
- printf("\nEl modo de video debe estar en 80 columnas.");
-
- exit(1);
-
- }
-
- if (modov==7)
-
- mem_video = (char far *) 0xb0000000; /*Monocromo*/
-
- else
-
- mem_video = (char far *) 0xb8000000; /*Color */
-
- do{
-
- }while (humo()); /*Mientras humo devuelva un 1 es que hay caracteres*/
-
- printf("Prueba de desaparicion de caracteres realizada");
-
- return(0);
-
- }
-
- int modo_video(void)
-
- {
-
- union REGS r;
-
- r.h.ah=15; /*obtiene el modo de video */
-
- return int86(0x10,&r,&r) & 255;
-
- }
-
- int humo(void)
-
- {
-
- register char far *p;
-
- int bandera=0;
-
- for (p=mem_video;p<mem_video+80*25*2;p++,p++)
-
- if ((*p!=0) && (*p!=32)){
-
- (*p)++;
-
- bandera=1;
-
- }
-
- return(bandera);
-
- }
-
- Antonio Javier García Martínez
-
- Granada
-
-
- GUARDAR Y RESTAURAR PANTALLAS
-
- Las siguientes rutinas realizadas en C++ son una mejora de las rutinas
- publicadas en el número de febrero para guardar y restaurar pantallas
- de texto. Estos procedimientos muestran su utilidad cuando abrimos un
- menú, cuadro de diálogo o ventana y al cerrarlo deseamos que
- reaparezca el contenido de la pantalla tal y como estaba
- anteriormente.
-
- La ventajas que ofrecen las nuevas rutinas es que trabajan
- directamente con la memoria de vídeo. Para ello se basan en el
- principio de que los modos de texto de 80x25 disponen de cuatro
- páginas de vídeo que normalmente no se utilizan. Estos nuevos
- procedimientos -«SaveScreen (...)» y «RestScreen(...)»- copian las
- pantallas a otra página, lo que permite que el acceso sea más rápido.
-
- Tan sólo presentan una desventaja producida por la limitación de
- páginas de vídeo disponibles, pues en el modo 80x25 sólo disponemos de
- tres páginas libres y en el modo 40x25 de siete páginas. En cada
- página libre podremos guardar una pantalla.
-
- El siguiente programa de ejemplo captura la pantalla de texto, despues
- espera a que se pulse una tecla, borra la pantalla y espera de nuevo
- otra pulsación de tecla, tras la cual restaura el contenido original
- de la pantalla.
-
- #include <stdio.h>
-
- #include <mem.h>
-
- void SaveScreen (unsigned short Pagina);
-
- void RestScreen (unsigned short Pagina);
-
- void main(void);
-
- {
-
- printf ("PC Actual");
-
- int c;
-
- SaveScreen (1);
-
- c=getchar();
-
- clrscr();
-
- c=getchar;
-
- RestScreen(1);
-
- }
-
-
- // Funciones Principales //
-
- void SaveScreen (unsigned short Pagina);
-
- {
- unsigned int Pos=Pagina*0x1000;
-
- movedata (0xB800, 0x0000, 0xB800, Pos, 4000);
-
- }
-
- void RestScreen (unsigned short Pagina);
-
- {
-
- unsigned int Pos=Pagina*0x1000;
-
- movedata (0xB800, Pos, 0xB800, 0x0000, 4000);
-
- }
-
-
- Daniel Sánchez Teodoro
-
- Granada
-
-
- ESCALA DE GRISES
-
- Esta rutina realizada en Turbo C, aunque fácilmente adaptable a Pascal
- o ensamblador, transforma la paleta de la pantalla MCGA o VGA 256
- colores (320 x 200 con 256 colores) a sus correspondientes valores de
- la escala de grises. En definitiva, cuando llamamos a esta función el
- gráfico de la pantalla se pone en blanco y negro, tal y como vemos en
- muchas máquinas recreativas.
-
- Para transformar la paleta de la pantalla a grises ejecutaremos
- gris(0), mientras que para devolver a su estado original una paleta
- convertida a escala de grises escribiremos gris(1).
-
- Las dos rutinas para gris se pueden incluir en el módulo principal del
- programa en C, pero en caso de que deseemos linkar esta función como
- un módulo separado no hay que olvidar incluir el fichero «.h» para
- acceder a ella.
-
- /* Función de transformación de grises
-
- #include <dos.h>
-
- #define GRIS 0
-
- #define COLOR 1
-
- void gris(void);
-
- static unsigned char paleta_antigua[256][3];
-
- static unsigned char activado;
-
- void gris (char modo)
-
- {
-
- switch(modo){
-
- case COLOR;
-
- if (!activado) break; /*sale si no hay grises */
-
- _ES = FP_SEG(paleta_antigua); /*Estas dos siempre primero */
-
- _DX = FP_OFF(paleta_antigua);
-
- _AX = 0x1012; /* Función BIOS para definir PALETA */
-
- _BX = 0;
-
- _CX = 256;
-
- geninterrupt (0x10); /* Llama a la BIOS */
-
- activado=~activado; /* Muta el indicador */
-
- break;
-
- case GRIS;
-
- if (activado) break; /*sale si ya hay grises */
-
- _ES = FP_SEG(paleta_antigua); /*Estas dos siempre primero */
-
- _DX = FP_OFF(paleta_antigua);
-
- _AX = 0x1017; /* Salva la paleta de color antigua */
-
- _BX = 0;
-
- _CX = 256;
-
- geninterrupt (0x10); /* Llama a la BIOS */
-
- _AX = 0x101B; /* Pasa a grises */
-
- _BX = 0;
-
- _CX = 256;
-
- geninterrupt (0x10); /* Llama a la BIOS */
-
- activado=~activado; /* Muta el indicador */
-
- break;
-
- }
-
- }
-
- Fichero «gris.h»:
-
- /* Cabecera del módulo transformador de grises vía BIOS (MCGA-VGA) */
-
- extern void gris(void);
-
- #define GRIS 0
-
- #define COLOR 1
-
- Luis Díaz Villanueva
-
- Madrid
-
- Comentario del Laboratorio: La rutina se basa en la utilización de la
- interrupción 10 de la BIOS (encargada de los servicios de vídeo),
- aunque más en concreto en la función 10, cuya misión es la gestión de
- los registros de la paleta de colores. La paleta de colores en el
- modo VGA 256 está formada por 256 registros (uno por color) con tres
- valores cada uno (para la cantidad de rojo, verde y azul de cada
- color)
-
- Para llevar a cabo el truco se hace uso de la subfunción 12, cuya
- misión es la asignación de un bloque de registros de color; la
- subfunción 17, que lee un bloque de registros de color, y, por último,
- de la subfunción 1B, que suma los valores de color para pasar a tonos
- de grises. Estas funciones necesitan tener cargado en ES la dirección
- del segmento donde se encuentra la tabla donde leeremos o grabaremos
- los registros de color de la paleta. Además, en DX debe cargarse el
- desplazamiento (offset) de dicha tabla.
-
- Para efectuar la llamada a la función cargamos el 10 (del número de
- función) en el registro AH y el número de subfunción en el registro
- AL. Por ejemplo, cuando ejecutamos «gris(0)» en el truco llamamos a
- la subfunción 12, por eso en este caso cargamos en AH el 10 y en AL el
- 12, lo que es equivalente a cargar 1012 en AX. Una vez que hemos
- cargado el valor de la función a emplear debemos pasar en BX el número
- de color desde el que queremos empezar a trabajar; en este caso nos
- interesa el primer color (el 0) para convertir toda la paleta.
- Además, en CX cargaremos el número de colores que queremos convertir.
- Por último, modificando los valores de BX y CX conseguiremos tratar
- sólo un determinado rango de colores. Tras haber cargado todos los
- valores en cada uno de los registros se efectúa la llamada a la
- interrupción 10.
-
-
- RUTINAS PARA LA PALETA
-
- Esta librería para C puede ser de gran utilidad para todos los
- programadores que utilicen cualquier modo gráfico y deseen «jugar» con
- la paleta de colores.
-
- La función «set_rgb» sirve para establecer los valores RGB, es decir,
- las cantidades de rojo, verde y azul (en este orden) que forman el
- color («col»). La función «get_rgb» efectúa el proceso contrario, es
- decir, dado el color «col» nos devuelve la cantidad de rojo, verde y
- azul que componen dicho color.
-
- También podremos utilizar «Make_gradiente» para crear una escala de
- gradientes. Como argumentos se le pasan los valores RGB (rojo, verde
- y azul) del color inicial y del color final, así como el color en que
- comienza la escala y el número de colores que la compondrán (si este
- último argumento es negativo se pueden obtener escalas hacia atras).
-
- Por último, la función «ciclo» se utiliza para conseguir que una
- sección de la paleta gire o rote sus colores. Se le pasan como
- argumentos el color inicial y final del segmento de paleta deseado.
- Con este efecto se consigue un resultado especialmente vistoso
- utilizándolo en un bucle, logrando un efecto semejante al utilizado en
- algunos programas de fractales (como el Fractint).
-
- Un ejemplo de esto último es:
-
- while (!kbhit())
-
- {
-
- ciclo(0,255);
-
- }
-
-
- La librería es la siguiente:
-
- #include <dos.h>
-
- typedef unsigned char byte;
-
- typedef struct
-
- {
-
- byte r;
-
- byte g;
-
- byte b;
-
- }rgb;
-
- void set_rgb (byte r, byte g, byte b, byte col);
-
- rgb get_rgb (byte col);
-
- void ciclo (byte inicio, byte fin);
-
- void make_gradiente (byte, byte, byte, byte, byte, byte, byte, int );
-
- void set_rgb (byte r, byte g, byte b, byte col)
-
- {
-
- outportb(0x3c8, col);
-
- outportb(0x3c9, r);
-
- outportb(0x3c9, g);
-
- outportb(0x3c9, b);
-
- }
-
- rgb get_rgb (byte col)
-
- {
-
- rgb result;
-
- outportb(0x3c7, col);
-
- result.r=inport(0x3c9);
-
- result.g=inport(0x3c9);
-
- result.b=inport(0x3c9);
-
- return (result);
-
- }
-
- void ciclo (byte inicio, byte fi)
-
- {
-
- int cont=0;
-
- rgb ci=get_rgb(inicio);
-
- rgb c;
-
- for (cont=inicio; cont <final; cont++)
-
- {
-
- c=get_rgb(cont+1);
-
- set_rgb(c.r, c.g, c.b, cont);
-
- }
-
- set_rgb(ci.r, ci.g, ci.b, final);
-
- }
-
- void make_gradiente (byte R1, byte G1, byte B1, byte R2,
-
- byte G2, byte B2, byte inicio, int numtonos)
-
- {
-
- int deltaR, deltaG, deltaB;
-
- int cont, sent = 1;
-
- int n=abs(numtonos);
-
- byte col=0;
-
- rgb c;
-
- if (n==0) return;
-
- deltaR=R2-R1;
-
- deltaG=G2-G1;
-
- deltaB=B2-B1;
-
- if (numtonos<0) sent=-1;
-
- for (col=ini, cont=0, cont<=n; cont++, col+=sent)
-
- {
-
- c.r =R1+(deltaR*cont/n);
-
- c.g =G1+(deltaR*cont/n);
-
- c.b =B1+(deltaR*cont/n);
-
- set_rgb(c.r, c.g, c.b, col);
-
- }
-
- }
-
- Fernando Moyano
-
- Pamplona
-
-
- CAMBIO DE LETRAS
-
- Las siguientes rutinas han de ser llamadas desde otra función, y
- permiten convertir los caracteres normales en cursivas, negritas y
- subrayadas. Es tarea fácil partir de estas rutinas para crear otras
- que hagan cualquier otra cosa, y es algo que puede ser útil para
- usarlo en algún programa, dándole un toque de distición.
-
- #include <dos.h>
-
- #include <conio.h>
-
- #include <stdio.h>
-
- typedef unsigned int word;
-
- typedef unsigned char byte;
-
- byte far* LoadFont()
-
- /*Esta rutina usa las fuentes de 16 bytes*/
-
- {
-
- word wSegment,wOffset;
-
- asm{
-
- mov di,bp
-
- mov ah,0x11
-
- mov al,0x30
-
- mov bh,6
-
- int 0x10
-
- push es
-
- push bp
-
- mov bp,di
-
- pop ax
-
- mov wOffset,ax
-
- pop ax
-
- mov wSegment,ax
-
- }
-
- return (byte far*)MK_FP(wSegment,wOffset);
-
- }
-
- void SetFont(byte far *pby)
-
- /*Esta rutina usa las fuentes de 16 bytes*/
-
- {
-
- asm{
-
- push bp
-
- mov ah,0x11
-
- mov al,0
-
- mov bh,16 /*16bytes por carácter*/
-
- mov bl,0
-
- mov cx,97 /*97 caracteres*/
-
- mov dl,'!' /*carácter a partir del cual comienzo*/
-
- mov dh,0
-
- les bp,pby
-
- int 0x10
-
- pop bp
-
- }
-
- }
-
- void Bold()
-
- /*Esta rutina usa las fuentes de 16 bytes*/
-
- {
-
- byte far *pbyOld,pbyNew[16*97];
-
- int i;
-
- pbyOld=LoadFont();
-
- for(i=0;i<16*97;i++)
-
- pbyNew[i]=(pbyOld[i+16*33]>>1)|pbyOld[i+16*33];
-
- SetFont(pbyNew);
-
- }
-
- void Underlined()
-
- /*Esta rutina usa las fuentes de 16 bytes*/
-
- {
-
- byte far *pbyOld,pbyNew[16*97];
-
- int i;
-
- pbyOld=LoadFont();
-
- for(i=0;i<16*97;i++)
-
- if(i%16==15)
-
- pbyNew[i]=0xFF;
-
- else
-
- pbyNew[i]=pbyOld[i+16*33];
-
-
- SetFont(pbyNew);
-
- }
-
- void Cursive()
-
- /*Esta rutina usa las fuentes de 16 bytes*/
-
- {
-
- byte far *pbyOld,pbyNew[16*97];
-
- int i;
-
- pbyOld=LoadFont();
-
- for(i=0;i<16*97;i++)
-
- switch(i%16)
-
- {
-
- case 2:
-
- case 3:
-
- pbyNew[i]=pbyOld[i+16*33]>>2;
-
- break;
-
- case 4:
-
- case 5:
-
- pbyNew[i]=pbyOld[i+16*33]>>1;
-
- break;
-
- case 10:
-
- case 11:
-
- pbyNew[i]=pbyOld[i+16*33]<<1;
-
- break;
-
- case 12:
-
- case 13:
-
- pbyNew[i]=pbyOld[i+16*33]<<2;
-
- break;
-
- default:
-
- pbyNew[i]=pbyOld[i+16*33];
-
- }
-
- SetFont(pbyNew);
-
- }
-
- Daniel Pérez Palomar
-
- Barcelona
-
-
-
- CONTROL DE LA IMPRESORA
-
- Esta rutina sirve para programas que deseen conocer el estado de la
- impresora antes de mandar algo a imprimir, y en el caso de que no esté
- correctamente conectada puedan mandar el código de error
- correspondiente.
-
- El programa está realizado en Borland C++ 2.0, y hace uso de la
- función «biosprint» de la librería «bios.h».
-
- Está función actúa bajo los registros de la BIOS y nos permitirá saber
- si nuestra impresora está ocupada, tiene algún error en el dispositivo
- de entrada/salida, si tiene papel, etc.
-
- La función «biosprint» trabaja devolviendo un valor que se guardará en
- este caso en la variable «printer». Según el valor que reciba
- sabremos su estado. Otra utilidad de esta función es la de
- reinicializar la impresora una vez ya conectada. Esto puede resultar
- de gran utilidad, si se desean eliminar los datos del buffer de la
- impresora cuando se está realizando un programa. Se hace cambiando el
- valor «estado» por 1, de tal modo que la impresora se reiniciará.
-
- #include <conio.h>
-
- #include <bios.h>
-
- #include <stdio.h>
-
- #define ESTADO 2
-
- #define PUERTO 0
-
- int printer;
-
- main ()
-
- {
-
- clrscr ();
-
- textcolor(cyan + blynk);
-
- cprintf ("\n ......... ESTADO DE LA IMPRESORA ..........");
-
- printer = biosprint (ESTADO, 0, PUERTO);
-
- /* La variable printer almacena el estado de la impresora */
-
- if (printer & 0x10) printf ("\n\nImpresora conectada...");
-
-
- else
-
- printf("\n\nLa impresora no está conectada...");
-
- if (printer & 0x08) printf("\nError en el dispositivo I/O...");
-
- else
-
- printf("\nNo hay error en el dispositivo I/O...");
-
- if (printer & 0x01) printf (\nPaso del tiempo adjudicado...");
-
- else
-
- printf("\nNO - paso del tiempo adjudicado...");
-
- if (printer & 0x20) printf ("\nLa impresora no encuentra el papel...");
-
- else
-
- printf("\nLa impresora tiene papel...");
-
- if (printer & 0x40) printf ("\nSI - Acuse de recibo...");
-
- else
-
- printf(\nNO - Acuse de recibo...");
-
- if (printer & 0x80) printf("\nImpresora no ocupada...");
-
- else
-
- printf("\nImpresora ocupada...");
-
- getch();
-
- exit(1);
-
- }
-
- Lluís Company Ordoño
-
- Terrassa (Barcelona)
-
-
- ELEGIR EL DIRECTORIO
-
- Todos nos hemos sentido tentados en alguna ocasión a escribir algún
- pequeño programa que nos facilitase las tareas de movernos por nuestro
- disco duro. Pero el principal inconveniente con el que topábamos era
- que un cambio en el árbol de directorios del mismo nos obligaba a
- reescribir o recompilar la utilidad creada.
-
- La siguiente rutina nos ofrece una interesante alternativa. En
- efecto, el programa «Eligdir» nos permite situarnos en cualquier
- subdirectorio de la unidad por defecto, con tan sólo algunas
- pulsaciones de teclas de función. Ocupa apenas 11 Kbytes y tan sólo
- lee los 10 primeros subdirectorios de cada nivel (lo que puede ser
- tanto una ventaja como un inconveniente).
-
- Su algoritmo de funcionamiento es el siguiente. En primer lugar lee
- las entradas en el directorio actual, almacenando en una cola los
- directorios encontrados. A continuación se pide por teclado la
- pulsación de una tecla de función y se salta al directorio asociado a
- la misma leyendo la cola anterior. El proceso se repite hasta que la
- entrada por teclado sea distinta de cualquiera de las teclas de
- función.
-
- Añadir por último que este programa fue escrito para el compilador
- Turbo C 2.0 de Borland, siendo recomendable su compilación en los
- modelos tiny o small.
-
- #include <dir.h>
-
- #include <stdio.h>
-
- #include <stdlib.h>
-
- #include <dos.h>
-
- #include <bios.h>
-
- char todos[]="*.*";
-
- /*patrón de búsqueda*/
-
- struct ffblk f;
-
- /*file control block*/
-
- int atributos=FA_DIREC;
-
- /*atributo de fichero=directorio*/
-
- int ret;
-
- /*resultado de funciones findfirst y findnext*/
-
- char diract[MAXDIR];
-
- /*cadena con el nombre del camino actual*/
-
- extern unsigned _stacklen=512;
-
- /*tamaño de pila y heap (mínimo)*/
-
- extern unsigned _heaplen=1024;
-
- struct cola
-
- /*cola de los directorios seleccionados*/
-
- {char nombre[13];
-
- struct cola *sig;
-
- } *pcab,*pcola;
-
- /*punteros a cabeza y fin de la cola*/
-
- void IniciaC()
-
- /*Inicia la cola, borrándola*/
-
- { struct cola *p1,*p2;
-
- if (pcab!=NULL)
-
- {p1=pcab;p2=pcab->sig;
-
- while(p2!=NULL)
-
- {free(p1);
-
- p1=p2;
-
- p2=p2->sig;
-
- }
-
- free(p1);
-
- pcab=NULL;
-
- }
-
- }
-
- void MeterC(cad)
-
- /*Mete un string en la cola*/
-
- char cad[13];
-
- {struct cola *p2;
-
- if ((p2=malloc(sizeof(*p2)))==NULL)
-
- {puts("No hay memoria suficiente");exit(0);}
-
- strcpy(p2->nombre,cad);
-
- p2->sig=NULL;
-
- if (pcab==NULL) pcab=p2;
-
- else pcola->sig=p2;
-
- pcola=p2;
-
- }
-
- EsvaciaC()
-
- /*Comprueba si la cola está vacía*/
-
- {return(pcab==NULL);}
-
- void BuscaDIR()
-
- /*Busca los directorios y los mete en la cola*/
-
- {short c=0;
-
- IniciaC();
-
- ret=findfirst(todos,&f,atributos);
-
- /*busca el primero*/
-
- if (ret==-1) return;
-
- /*si no está, salir*/
-
- if (f.ff_attrib==FA_DIREC && (f.ff_name[0]!='.'))
-
- /*si es directorio válido*/
-
- {MeterC(f.ff_name);c++;}
-
- /*meterlo en cola*/
-
- for(;;)
-
- {ret=findnext(&f);
-
- /*busca el siguiente*/
-
- if ((ret==-1) || (c>10)) break;
-
- /*si no encontrado o hay más de 10, salir*/
-
- if (f.ff_attrib==FA_DIREC) {MeterC(f.ff_name);c++;}
-
- }
-
- if (EsvaciaC()) {puts("No encontré directorios");exit(0);}
-
- }
-
- void Eligeopcion()
-
- /*Muestra los directorios seleccionados y pide uno de ellos*/
-
- {struct cola *p;
-
- int c,d;
-
- int tecla;
-
- getcurdir(0,diract);
-
- /*escribe directorio actual*/
-
- printf ("\n\n DIRECTORIO ACTUAL : \\%s",diract);
-
- puts ("\n Elige directorio: ");
-
- for(p=pcab,c=1;p!=NULL && c<=10;p=p->sig,c++)
-
- printf ("\n F%d - %s",c,p->nombre);
-
- puts ("\n OTRA CUALQUIERA - fin");
-
- tecla=bioskey(0)>>8;
-
- /*obtiene código tecla pulsada*/
-
- if ((tecla<0x3b)||(tecla>0x44)) exit(0);
-
- /*si no es tecla función, salir*/
-
- tecla-=0x3b;
-
- for(p=pcab,d=0;(tecla>d) && (p!=NULL);p=p->sig,d++);
-
- /*ir a dir seleccionado*/
-
- chdir(p->nombre);
-
- }
-
- main() /*Rutina principal*/
-
- {BuscaDIR();
-
- while(!EsvaciaC())
-
- {Eligeopcion();
-
- BuscaDIR();
-
- }
-
- }
-
- Gonzalo León Manzano
-
- Albacete
-
-
- EFECTO DE SOMBREADO
-
- Con esta función en C podemos dotar a nuestros programas de ventanas y
- menús con sombra. Las cajas son sencillas de hacer con las funciones
- y procedimientos incluidos en C, pero la dificultad surge al crear las
- sombras. Esta función nos ayudará durante el proceso de sombreado.
-
- El truco está en leer los caracteres adecuados de la pantalla y
- cambiarles el atributo que llevan asociado, es decir, el color de
- primer plano y el de fondo. El nuevo atributo ha de ser gris sobre
- negro.
-
- La siguiente función se usa para crear el efecto descrito alrededor de
- una región rectangular de coordenadas (x1,y1) (x2,y2).
-
- // Esta función dibuja una "sombra" en función de las coordenadas
- dadas
-
- // Se supone que se habrá dibujado una caja con esas mismas
- coordenadas
-
- // Para hacer la sombra se cambia el atributo de los caracteres
- adecuados
-
- // a gris sobre negro
-
- void Shadow(int x1,int y1,int x2,int y2)
-
- {
-
- int j=0;
-
- char ch;
-
- union REGS r;
-
- // Se dibuja el lado inferior de la sombra
-
- for(j=x1+2;j<x2+3;j++)
-
- {
-
- gotoxy(j,y2+1); // coloco el cursor en la posición adecuada
-
- r.h.ah=0x08;
-
- r.h.bh=0x00;
-
- int86(0x10,&r,&r); // consigo el carácter de esa posición
-
- ch=r.h.al; // ch contiene el carácter
-
- textattr(7); // cambio el atributo del carácter
-
- putch(ch); // y lo pongo de nuevo
-
- }
-
- //-- se dibuja el lado derecho de la sombra --
-
- for(j=y1+1;j<y2+1;j++)
-
- {
-
- gotoxy(x2+1,j); // coloco el cursor en la posición adecuada
-
- r.h.ah=0x08;
-
- r.h.bh=0x00;
-
- int86(0x10,&r,&r); // consigo el carácter de esa posición
-
- ch=r.h.al; // ch contiene el carácter
-
- textattr(7); // cambio el atributo del carácter
-
- putch(ch); // y lo pongo de nuevo
-
- }
-
- for(j=y1+1;j<y2+1;j++)
-
- {
-
- gotoxy(x2+2,j); // coloco el cursor en posición
-
- r.h.ah=0x08;
-
- r.h.bh=0x00;
-
- int86(0x10,&r,&r); // consigo el carácter adecuado
-
- ch=r.h.al; // ch contiene el carácter
-
- textattr(7); // cambio el atributo del carácter
-
- putch(ch); // y lo vuelvo a colocar en su sitio
-
- }
-
- }
-
- Daniel Sánchez Teodoro
-
- Granada
-
-
- DESARROLLA TUS PROPIOS ESTEREOGRAMAS
-
- Con esta rutina podemos realizar estereogramas de una sola imagen.
- Los estereogramas son esas extrañas imágenes (tan de moda hoy en día)
- que «esconden» objetos en tres dimensiones, pero que pueden verse
- empleando una determinada técnica. Demetrio Fernández nos ha mandado
- una rutina creada por él mismo que permite, a partir de una imagen,
- desarrollar un estereograma. Está escrita en C y sorprende por su
- pequeño tamaño, pues tan sólo ocupa menos de 60 líneas.
-
- Para sacar provecho de todas sus prestaciones basta con crear el
- dibujo o imagen, ponerla en pantalla y luego llamar al procedimiento
- «pantalla».
-
- unsigned rep=40;
-
- // ancho de repetición
-
- unsigned aleatorio[200];
-
- // patrón con el que trabaja el programa
-
- unsigned aleatorio2[200];
-
- // patrón original
-
- unsigned maximo=40;
-
- //igual que rep pero este es temporal
-
- unsigned NPUNTOS=1;
-
- //el número de puntos que se saltan
-
- unsigned paralelo=1;
-
- // modo de visualización en paralelo o cruzado
-
- // hace un simple negativo de la imagen
-
- void genera(unsigned ini,unsigned fin)
-
- // cuando hay que aumentar el aleatorio
-
- // mete trozos del aleatorio2
-
- {
-
- int i,j,d;
-
- d=fin-ini;
-
- j=random(rep-d);
-
- for(i=ini;i<fin;i++)
-
- {aleatorio[i]=aleatorio2[j+i-ini];}
-
- }
-
- void genera2(unsigned *tabl,unsigned ini,unsigned fin)
-
- // aquí genera puntos aleatorios pero
-
- // podéis poner lo que queráis como patron
-
- {
-
- int i;
-
- for(i=ini;i<fin;i++)
-
- {tabl[i]=random(getmaxcolor());}
-
- }
-
- void adelante(unsigned ini,unsigned salto)
-
- // incrementamos profundidad en la imagen
-
-
- {
-
- unsigned i;
-
- for (i=maximo;i>ini;i--) aleatorio[i+NPUNTOS*salto]=aleatorio[i];
-
- maximo+=NPUNTOS*salto;
-
- genera(i,i+NPUNTOS*salto);
-
- }
-
- void atras(unsigned ini,unsigned salto)
-
- // decrementamos profundidad en la imagen
-
- {
-
- unsigned i;
-
- for (i=ini;i<maximo;i++) aleatorio[i]=aleatorio[i+NPUNTOS*salto];
-
- maximo-=NPUNTOS*salto;
-
- }
-
- void rastrealinea(unsigned numlin)
-
- // genera cada línea
-
- {
-
- unsigned i,j,k;
-
- unsigned color;
-
- color=0;
-
- maximo=rep;
-
- genera2(aleatorio,numlin,0,maximo*2);
-
- genera2(aleatorio2,numlin,0,maximo*2);
-
- j=0;
-
- for(i=0;i<getmaxx();i++)
-
- {if (paralelo) k=15-getpixel(i,numlin);
-
- else k=getpixel(i,numlin);
-
- if (k!=color)
-
- {if (k<color) adelante(j,color-k);
-
- else atras(j,k-color);
-
- color=k;}
-
- putpixel(i,numlin,aleatorio[j]);
-
- j=(j+1)%maximo;}
-
- }
-
- void pantalla(void)
-
- // hace un estereograma de toda la pantalla
-
- {
-
- unsigned i;
-
- for (i=0;i<=getmaxy();i++)
-
- {
-
- if (i%2) rastrealinea(i);
-
- else rastrealinea(480-i);}
-
- }
-
- Nota sobre la visualización: Christopher W. Tyler fue el creador de
- los estereogramas de una sola imagen. Este tipo de estereogramas no
- son en verdad una sola imagen, sino siete u ocho imágenes iguales
- puestas unas juntas con las otras hasta formar una única imagen y el
- efecto de profundidad. La técnica de visualización consiste en poner
- el punto focal detras de la página que estamos viendo, tratando de
- situar la vista más allá de la hoja. Se consigue acercando la imagen
- (en este caso la pantalla) a los ojos y después separándola (en este
- caso la cabeza) hasta que veamos las tres dimensiones.
-
- Demetrio Fernández Alvarez
-
- Oviedo
-
-
- TRATAMIENTO DE IMAGENES
-
- Las siguientes rutinas son dos procedimientos que nos van a permitir,
- en primer lugar, capturar cualquier imagen que se pueda sacar por
- pantalla (incluso aquellas de 256 colores), para convertirla en un
- formato reconocible por la segunda rutina, que será la que dibujará
- esa misma imagen pero adaptándola a un polígono que le pasaremos como
- parámetro.
-
- Para utilizar estas rutinas en los nuevos programas hay que incluir el
- fichero «trans_ima.h», además de indicar a nuestro compilador que debe
- enlazar nuestro programa y el fichero «trans_ima.c».
-
- El programa «Trans_ima.h» es el siguiente:
-
- /* TRANSFORMA IMAGEN
-
- Este conjunto de rutinas está pensado para capturar imágenes y luego
- adaptarlas a cualquier polígono, sea o no rectangular.
-
- - captura: Coge una zona de la pantalla gráfica y la captura en el
- formato t_imagen.
-
- - D_dibuja: Adapta la imagen que se le pasa como parámetro al
- polígono que le indicamos en la variable de tipo t_puntos.
-
- El tipo t_puntos no es más que un registro con cuatro puntos que
- señalan los vértices de un polígono.
-
- */
-
- struct t_imagen
-
- {unsigned tam_max_x,tam_max_y;
-
- unsigned char huge *ptr;
-
- };
-
- struct t_punto
-
- {int x,y;};
-
- struct t_puntos
-
- {struct t_punto p1,p2,p3,p4;};
-
- void D_dibuja (struct t_imagen,struct t_puntos);
-
- struct t_imagen captura (int,int,int,int);
-
-
- El programa «Trans_ima.c» es el siguiente:
-
- #include "alloc.h"
-
- #include "graphics.h"
-
- #include "math.h"
-
- #include "trans_ima.h"
-
- struct t_coef
-
- {float x,y;};
-
- struct t_coefs
-
- {struct t_coef c1,c2,c3,c4;};
-
- void calcula_coef (struct t_puntos,struct t_coefs *);
-
- void calcula_incremento_a (struct t_puntos,float *);
-
- void calcula_incremento_b (struct t_puntos puntos,float *incb);
-
- struct t_punto S_destino (float,float,struct t_coefs);
-
- struct t_punto S_origen (struct t_imagen,float,float);
-
- int color_origen (struct t_imagen,struct t_punto);
-
- struct t_imagen captura (int x1,int y1,int x2,int y2)
-
- {unsigned i,j;
-
- struct t_imagen imagen;
-
- unsigned seg;
-
- int error;
-
- imagen.ptr = farmalloc ((unsigned long) (y2-y1+1)*(x2-x1+1));
-
- if (imagen.ptr != NULL)
-
- {imagen.tam_max_x = x2-x1;
-
- imagen.tam_max_y = y2-y1;
-
- for (i=0;i<=y2-y1;i++)
-
- {for (j=0;j<=x2-x1;j++)
-
- {imagen.ptr [(unsigned long) i*(x2-x1+1)+j] = getpixel (x1+j,y1+i);}
-
- }
-
- }
-
- return (imagen);
-
- }
-
- void calcula_coef (struct t_puntos puntos,struct t_coefs *coef)
-
- {
-
- coef->c1.x = puntos.p1.x-puntos.p2.x+puntos.p3.x-puntos.p4.x;
-
- coef->c1.y = puntos.p1.y-puntos.p2.y+puntos.p3.y-puntos.p4.y;
-
- coef->c2.x = puntos.p4.x-puntos.p3.x;
-
- coef->c2.y = puntos.p4.y-puntos.p3.y;
-
- coef->c3.x = puntos.p2.x-puntos.p3.x;
-
- coef->c3.y = puntos.p2.y-puntos.p3.y;
-
- coef->c4.x = puntos.p3.x;
-
- coef->c4.y = puntos.p3.y;
-
- }
-
- struct t_punto S_destino (float alfa,float beta,struct t_coefs coef)
-
- {struct t_punto p;
-
- p.x = (int) (alfa*beta*coef.c1.x + alfa*coef.c2.x + beta*coef.c3.x +
- coef.c4.x);
-
- p.y = (int) (alfa*beta*coef.c1.y + alfa*coef.c2.y + beta*coef.c3.y +
- coef.c4.y);
-
- return (p);
-
- }
-
- struct t_punto S_origen (struct t_imagen imagen,float alfa,float beta)
-
- {struct t_punto p;
-
- p.x = imagen.tam_max_x -(int) (beta*imagen.tam_max_x);
-
- p.y = imagen.tam_max_y -(int) (alfa*imagen.tam_max_y);
-
- return (p);
-
- }
-
- int color_origen (struct t_imagen imagen,
-
- struct t_punto p)
-
- {
-
- return (imagen.ptr [(unsigned long) p.y*(imagen.tam_max_x+1)+p.x]);
-
- }
-
- void calcula_incremento_a (struct t_puntos puntos,float *inca)
-
- {unsigned dist1,dist2;
-
- float dist;
-
- int vx,vy;
-
- vx = abs (puntos.p2.x-puntos.p1.x);
-
- vy = abs (puntos.p2.y-puntos.p1.y);
-
- dist1 = ((vx > vy) ? vx : vy);
-
- vx = abs (puntos.p3.x-puntos.p4.x);
-
- vy = abs (puntos.p3.y-puntos.p4.y);
-
- dist2 = ((vx > vy) ? vx : vy);
-
- dist = (((dist1) > (dist2)) ? (dist1) : (dist2));
-
- *inca = 1/(dist+1);
-
- }
-
- void calcula_incremento_b (struct t_puntos puntos,float *incb)
-
- {unsigned dist1,dist2;
-
- float dist;
-
- int vx,vy;
-
- vx = abs (puntos.p4.x-puntos.p1.x);
-
- vy = abs (puntos.p4.y-puntos.p1.y);
-
- dist1 = ((vx > vy) ? vx : vy);
-
- vx = abs (puntos.p2.x-puntos.p3.x);
-
- vy = abs (puntos.p2.y-puntos.p3.y);
-
- dist2 = ((vx > vy) ? vx : vy);
-
- dist = (((dist1) > (dist2)) ? (dist1) : (dist2));
-
- *incb = 1/(dist+1);
-
- }
-
- void D_dibuja (struct t_imagen origen,
-
- struct t_puntos puntos)
-
- {float alfa,beta;
-
- struct t_punto p;
-
- struct t_coefs coef;
-
- int color;
-
- float inca,incb;
-
- calcula_incremento_a (puntos,&inca);
-
- calcula_incremento_b (puntos,&incb);
-
- calcula_coef (puntos,&coef);
-
- for (alfa=0;alfa<=1;alfa+=inca)
-
- for (beta=0;beta<=1;beta+=incb)
-
- {p = S_origen (origen,alfa,beta);
-
- color = color_origen (origen,p);
-
- p = S_destino (alfa,beta,coef);
-
- putpixel (p.x,p.y,color);
-
- }
-
- }
-
- Siguiendo estos pasos, tenemos a nuestra disposición dos rutinas:
-
- - struct t_imagen captura(int x1, int y1, int x2, int y2)
-
- - void D_dibuja (struct t_imagen imagen, struct t_puntos p)
-
- La primera función captura el mapa de bits comprendido entre los
- puntos (x1,y1) y (x2,y2), devolviendo un registro de tipo t_imagen, en
- el que queda almacenada.
-
- El segundo procedimiento coge la imagen previamente capturada y la
- dibuja adaptándola al polígono de cuatro vértices indicado por la
- variable p.
-
- Hemos de tener en cuenta que la imagen capturada se almacena en
- memoria principal como una matriz de char, con un byte por cada
- pixel que capturemos. Por lo que si los bitmaps van a ser muy
- grandes tendremos que compilar el programa en modelos como «Compact».
-
- En el siguiente programa vemos un ejemplo de la utilización de estas
- rutinas:
-
- #include "alloc.h"
-
- #include "graphics.h"
-
- #include "stdio.h"
-
- #include "fcntl.h"
-
- #include "io.h"
-
- #include "trans_ima.h"
-
- struct t_imagen carga_origen (char *);
-
- int inicia_graficos ();
-
- int main ()
-
- {struct t_puntos puntos;
-
- struct t_imagen origen;
-
- char *cadena = "PC-ACTUAL";
-
- char *aux = " \0";
-
- int i;
-
- inicia_graficos ();
-
- /* PRIMERO SIMPLEMENTE DIBUJAMOS UNA IMAGEN EN LA PANTALLA */
-
- settextstyle (DEFAULT_FONT,HORIZ_DIR,3);
-
- moveto (0,0);
-
- for (i=0;i < strlen (cadena);i++)
-
- {setcolor (i+1);
-
- strnset (aux,cadena [i],1);
-
- outtext (aux);
-
- }
-
- setcolor (i+1);
-
- line (0,textheight (cadena),textwidth (cadena),textheight (cadena));
-
- /* CAPTURAMOS LA PARTE DE LA PANTALLA QUE NOS INTERESA EN UNA VARIABLE
- DE TIPO ORIGEN */
-
- origen.tam_max_x = textwidth (cadena);
-
- origen.tam_max_y = textheight (cadena);
-
- origen = captura (0,0,origen.tam_max_x,origen.tam_max_y);
-
- settextstyle (DEFAULT_FONT,HORIZ_DIR,1);
-
- setcolor (WHITE);
-
- outtextxy (0,getmaxy ()-textheight ("P"),
-
- "Pulsa una tecla para ver la imagen transformada...");
-
- getch ();
-
- if (origen.ptr != NULL) /* ¿HA HABIDO ERROR EN ASIGNACION DE MEMORIA? */
-
- {cleardevice ();
-
- /* DIBUJAMOS LA IMAGEN TRANSFORMADA */
-
- puntos.p1.x = 0;puntos.p1.y = 0;
-
- puntos.p2.x = 0;puntos.p2.y = getmaxy ();
-
- puntos.p3.x = getmaxx ()/2-50;puntos.p3.y = getmaxy ()/2+40;
-
- puntos.p4.x = getmaxx ()/2-50;puntos.p4.y = getmaxy ()/2-40;
-
- D_dibuja (origen,puntos);
-
- puntos.p1.x = getmaxx ()/2-40;puntos.p1.y = getmaxy ()/2+50;
-
- puntos.p2.x = 0;puntos.p2.y = getmaxy ();
-
- puntos.p3.x = getmaxx ();puntos.p3.y = getmaxy ();
-
- puntos.p4.x = getmaxx () /2+40;puntos.p4.y = getmaxy ()/2+50;
-
- D_dibuja (origen,puntos);
-
- puntos.p3.x = getmaxx ()/2+50;puntos.p3.y = getmaxy ()/2+40;
-
- puntos.p2.x = getmaxx ();puntos.p2.y = getmaxy ();
-
- puntos.p1.x = getmaxx ();puntos.p1.y = 0;
-
- puntos.p4.x = getmaxx ()/2+50;puntos.p4.y = getmaxy ()/2-40;
-
- D_dibuja (origen,puntos);
-
- puntos.p2.x = 0;puntos.p2.y = 0;
-
- puntos.p1.x = getmaxx ()/2-40;puntos.p1.y = getmaxy ()/2-50;
-
- puntos.p4.x = getmaxx ()/2+40;puntos.p4.y = getmaxy ()/2-50;
-
- puntos.p3.x = getmaxx ();puntos.p3.y = 0;
-
- D_dibuja (origen,puntos);
-
- free ((void *) origen.ptr);
-
- getch ();
-
- }
-
- else {closegraph ();
-
- printf ("\nError en asignacion de memoria\n");
-
- exit (1);
-
- }
-
- closegraph ();
-
- return (0);
-
- }
-
- int inicia_graficos ()
-
- {int driver,modo,errorcode;
-
- driver = DETECT;
-
- initgraph (&driver,&modo,"");
-
- errorcode = graphresult();
-
- if (errorcode != grOk)
-
- {
-
- printf("Error en graficos: %s\n", grapherrormsg(errorcode));
-
- printf("Pulsa una tecla para terminar.");
-
- getch();
-
- exit(1);
-
- }
-
- return (graphresult ());
-
- }
-
-
- Marcial Martínez López
-
- Valencia
-
-
-
-
-
-